package com.hibernate.hrm.controller.contract;

import com.hibernate.hrm.entity.Contract;
import com.hibernate.hrm.entity.Department;
import com.hibernate.hrm.entity.User;
import com.hibernate.hrm.entity.dto.contract.*;
import com.hibernate.hrm.service.contract.ContractAttachmentService;
import com.hibernate.hrm.service.contract.ContractService;
import lombok.RequiredArgsConstructor;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.http.HttpHeaders;
import org.springframework.http.HttpStatus;
import org.springframework.http.MediaType;
import org.springframework.http.ResponseEntity;
import org.springframework.security.core.annotation.AuthenticationPrincipal;
import org.springframework.stereotype.Controller;
import org.springframework.ui.Model;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;

import java.util.List;

@Controller
@RequestMapping("/contract")
@RequiredArgsConstructor
public class ContractController {

    private final ContractService contractService;
    private final ContractAttachmentService attachmentService;

    @GetMapping
    public String contractListPage(
            @RequestParam(value = "departmentId", required = false) Integer departmentId,
            @RequestParam(value = "contractType", required = false) String contractType,
            @RequestParam(value = "status", required = false) String status,
            @RequestParam(value = "page", defaultValue = "0") int page,
            @RequestParam(value = "size", defaultValue = "10") int size,
            @AuthenticationPrincipal User currentUser,
            Model model) {

        ContractQueryDTO queryDTO = new ContractQueryDTO();
        queryDTO.setDepartmentId(departmentId);

        if (contractType != null && !contractType.isEmpty()) {
            queryDTO.setContractType(Contract.ContractType.valueOf(contractType));
        }

        if (status != null && !status.isEmpty()) {
            queryDTO.setStatus(Contract.ContractStatus.valueOf(status));
        }

        // 设置分页参数
        Pageable pageable = PageRequest.of(page, size, Sort.by("contractId").descending());
        queryDTO.setPageable(pageable);

        Page<ContractDTO> contracts = contractService.getContractList(queryDTO, currentUser);

        // 处理空数据情况
        if (contracts.getTotalElements() == 0) {
            pageable = PageRequest.of(0, size, Sort.by("contractId").descending());
            queryDTO.setPageable(pageable);
            contracts = contractService.getContractList(queryDTO, currentUser);
        }

        List<Department> departments = contractService.getAccessibleDepartments(currentUser);

        model.addAttribute("contracts", contracts);
        model.addAttribute("departments", departments);
        model.addAttribute("currentDepartmentId", departmentId);
        model.addAttribute("currentContractType", contractType);
        model.addAttribute("currentStatus", status);
        model.addAttribute("currentUser", currentUser);
        model.addAttribute("roleIdValue", currentUser.getRoleId().getRoleId());
        model.addAttribute("contractTypes", Contract.ContractType.values());
        model.addAttribute("statuses", Contract.ContractStatus.values());

        return "contract";
    }

    //终止合同
    @PostMapping("/terminate/{id}")
    public String terminateContract(
            @PathVariable("id") Integer contractId,
            @AuthenticationPrincipal User currentUser) {
        contractService.terminateContract(contractId, currentUser);
        return "redirect:/contract";
    }

    //详情
    @GetMapping("/view/{id}")
    public String viewContract(
            @PathVariable("id") Integer contractId,
            @AuthenticationPrincipal User currentUser,
            Model model) {

        ContractDetailDTO contractDetail = contractService.getContractDetail(contractId, currentUser);
        List<ContractAttachmentDTO> attachments = attachmentService.getAttachmentsByContractId(contractId);
        model.addAttribute("contract", contractDetail);
        model.addAttribute("currentUser", currentUser);
        model.addAttribute("attachments", attachments);
        return "contract-view";
    }

    //导出合同
    @GetMapping("/export/{id}")
    public ResponseEntity<byte[]> exportContract(
            @PathVariable("id") Integer contractId,
            @AuthenticationPrincipal User currentUser) {

        byte[] wordBytes = contractService.exportContractToWord(contractId, currentUser);

        HttpHeaders headers = new HttpHeaders();
        headers.setContentType(MediaType.APPLICATION_OCTET_STREAM);
        headers.setContentDispositionFormData("attachment",
                "contract_" + contractId + ".docx");

        return new ResponseEntity<>(wordBytes, headers, HttpStatus.OK);
    }

    //编辑合同
    @GetMapping("/edit/{id}")
    public String editContractPage(
            @PathVariable("id") Integer contractId,
            @AuthenticationPrincipal User currentUser,
            Model model) {

        ContractDetailDTO contract = contractService.getContractForEdit(contractId, currentUser);
        List<ContractAttachmentDTO> attachments = attachmentService.getAttachmentsByContractId(contractId);

        model.addAttribute("contract", contract);
        model.addAttribute("attachments", attachments);
        model.addAttribute("currentUser", currentUser);
        model.addAttribute("contractTypes", Contract.ContractType.values());

        return "contract-edit";
    }

    @PostMapping("/edit/{id}")
    public String updateContract(
            @PathVariable("id") Integer contractId,
            @ModelAttribute ContractEditDTO editDTO,
            @AuthenticationPrincipal User currentUser) {

        editDTO.setContractId(contractId);
        contractService.updateContract(editDTO, currentUser);

        return "redirect:/contract/view/" + contractId;
    }

    @PostMapping("/upload-attachment/{id}")
    @ResponseBody
    public ResponseEntity<ContractAttachmentDTO> uploadAttachment(
            @PathVariable("id") Integer contractId,
            @RequestParam("file") MultipartFile file,
            @AuthenticationPrincipal User currentUser) {

        ContractAttachmentDTO attachment = attachmentService.uploadAttachment(
                contractId, file, currentUser.getUserId());

        return ResponseEntity.ok(attachment);
    }

    @DeleteMapping("/delete-attachment/{contractId}/{attachmentId}")
    @ResponseBody
    public ResponseEntity<Void> deleteAttachment(
            @PathVariable Integer contractId,
            @PathVariable Integer attachmentId,
            @AuthenticationPrincipal User currentUser) {

        attachmentService.deleteAttachment(contractId, attachmentId);
        return ResponseEntity.noContent().build();
    }
}
